package com.sky.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.sky.dto.SetmealDTO;
import com.sky.dto.SetmealPageQueryDTO;
import com.sky.entity.Setmeal;
import com.sky.entity.SetmealDish;
import com.sky.exception.DeletionNotAllowedException;
import com.sky.mapper.SetmealDishMapper;
import com.sky.mapper.SetmealMapper;
import com.sky.service.SetmealService;
import com.sky.vo.SetmealVO;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.stream.Collectors;

@Service
public class SetmealServiceImpl extends ServiceImpl<SetmealMapper, Setmeal> implements SetmealService {

    @Autowired
    private SetmealDishMapper setmealDishMapper;
    @Autowired
    private SetmealMapper setmealMapper;

    /**
     * 新增套餐，同时保存套餐和菜品的关联关系
     * 使用MyBatis-Plus的save方法和循环插入关联关系
     */
    @Override
    @Transactional
    public void saveWithDish(SetmealDTO setmealDTO) {
        // 1. 保存套餐基本信息
        Setmeal setmeal = new Setmeal();
        BeanUtils.copyProperties(setmealDTO, setmeal);
        this.save(setmeal);

        // 2. 保存套餐与菜品的关联关系
        List<SetmealDish> setmealDishes = setmealDTO.getSetmealDishes().stream()
                .map(dish -> {
                    SetmealDish setmealDish = new SetmealDish();
                    BeanUtils.copyProperties(dish, setmealDish);
                    setmealDish.setSetmealId(setmeal.getId());
                    return setmealDish;
                })
                .collect(Collectors.toList());

        // 循环插入关联关系（因为MyBatis-Plus的批量插入一般针对简单的批量插入场景，这里关联关系插入可能涉及更多逻辑，故采用循环插入示例）
        for (SetmealDish setmealDish : setmealDishes) {
            setmealDishMapper.insert(setmealDish);
        }
    }

    /**
     * 批量删除套餐
     * 使用MyBatis-Plus的批量删除方法和条件删除关联关系
     */
    @Override
    @Transactional
    public void deleteBatch(List<Long> ids) {
        // 1. 检查套餐是否在售，如果在售则不能删除
        LambdaQueryWrapper<Setmeal> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.in(Setmeal::getId, ids)
                .eq(Setmeal::getStatus, 1);
        int count = (int) this.count(queryWrapper);
        if (count > 0) {
            throw new DeletionNotAllowedException("套餐中包含在售菜品，无法删除");
        }

        // 2. 删除套餐基本信息
        this.removeByIds(ids);

        // 3. 删除套餐与菜品的关联关系
        LambdaQueryWrapper<SetmealDish> dishQueryWrapper = new LambdaQueryWrapper<>();
        dishQueryWrapper.in(SetmealDish::getSetmealId, ids);
        setmealDishMapper.delete(dishQueryWrapper);
    }

    /**
     * 修改套餐信息
     * 使用MyBatis-Plus的更新方法结合删除和插入关联关系逻辑
     */
    @Override
    @Transactional
    public void update(SetmealDTO setmealDTO) {
        // 1. 更新套餐基本信息
        Setmeal setmeal = new Setmeal();
        BeanUtils.copyProperties(setmealDTO, setmeal);
        this.updateById(setmeal);

        // 2. 先删除原有的套餐与菜品关联关系
        LambdaQueryWrapper<SetmealDish> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(SetmealDish::getSetmealId, setmealDTO.getId());
        setmealDishMapper.delete(queryWrapper);

        // 3. 重新添加新的关联关系
        List<SetmealDish> setmealDishes = setmealDTO.getSetmealDishes().stream()
                .map(dish -> {
                    SetmealDish setmealDish = new SetmealDish();
                    BeanUtils.copyProperties(dish, setmealDish);
                    setmealDish.setSetmealId(setmealDTO.getId());
                    return setmealDish;
                })
                .collect(Collectors.toList());

        // 循环插入新的关联关系（同新增时的插入逻辑说明）
        for (SetmealDish setmealDish : setmealDishes) {
            setmealDishMapper.insert(setmealDish);
        }
    }

    /**
     * 套餐起售停售
     * 使用MyBatis-Plus的条件更新方法
     */
    @Override
    public void startOrStop(Integer status, Long id) {
        LambdaUpdateWrapper<Setmeal> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(Setmeal::getId, id)
                .set(Setmeal::getStatus, status);
        this.update(updateWrapper);
    }



    /**
     * 根据ID查询套餐详情（包含菜品关联信息）
     */
    @Override
    public SetmealDTO getByIdWithDetails(Long id) {
        Setmeal setmeal = this.getById(id);
        if (setmeal == null) {
            return null;
        }
        SetmealDTO setmealDTO = new SetmealDTO();
        BeanUtils.copyProperties(setmeal, setmealDTO);

        // 查询关联的菜品信息
        LambdaQueryWrapper<SetmealDish> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(SetmealDish::getSetmealId, id);
        List<SetmealDish> setmealDishes = setmealDishMapper.selectList(queryWrapper);

        // 将菜品信息设置到DTO中（假设SetmealDTO有合适的字段接收菜品关联信息，比如List<SetmealDishVO>之类的）
        // 这里可能需要进一步转换为VO等操作，示例简化处理
        setmealDTO.setSetmealDishes(setmealDishes);

        return setmealDTO;
    }

    @Override
    public IPage<Setmeal> pageSetmeal(IPage<Setmeal> page, SetmealPageQueryDTO setmealPageQueryDTO) {
        return setmealMapper.pageSetmeal(page, setmealPageQueryDTO);
    }
}